<cfscript>
	// @ Author Qasim Rasheed (qasimrasheed@gmail.com)
	// Original idea taken by ColdSpring lexicon by Nathan Strutz.
	// Initializes ColdSpring into the current application scope (respecting the fusebox application key). This tag accepts one of more bean tag as children
	// usage:
	// 1. add the lexicon declaration to your circuit file:
	//    <circuit xmlns:cs="coldspring/">
	// 2. use the verb in a fuseaction:
	//    <cs:initialize  coldspringfactory="servicefactory" defaultproperties="default coldspring properties">
	//			<cs:bean beanDefinitionFile="..." />
	//			more bean tags......
	//    </cs:initialize>
	//
	if (fb_.verbInfo.executionMode is "start") {
		// coldspringfactory is optional:
		fb_.coldspringfactory = 'servicefactory';
        if (structKeyExists(fb_.verbInfo.attributes,"coldspringfactory")) {
            fb_.coldspringfactory = '#fb_.verbInfo.attributes.coldspringfactory#';
        }

        // default properties is optional:
        fb_.defaultproperties = '##structnew()##';
        if (structKeyExists(fb_.verbInfo.attributes,"defaultproperties" ) ) {
            fb_.defaultproperties = fb_.verbInfo.attributes.defaultproperties;
        }

        // useexisting is optional and must validate boolean
        fb_.useexisting = false;
        if (structKeyExists(fb_.verbInfo.attributes,"useexisting" ) ) {
        	if (isBoolean(fb_.verbInfo.attributes.useexisting)) {
        		fb_.useexisting = fb_.verbInfo.attributes.useexisting;
        	}
            else {
	        	fb_throw("fusebox.badGrammar.attributeValidation",
							"Type mismatch for 'useexisting' attribute.",
							"Type mismatch for 'useexisting' attribute - must be a boolean.  Current value is #fb_.verbInfo.attributes.useexisting#");
            }
        }

       	// if it has no bean tag as children.
        if ( not fb_.verbInfo.hasChildren ) {
        	fb_throw("fusebox.badGrammar.childTagMissing",
						"Child bean tag is missing",
						"Child bean tag is missing for verb 'initialize' in fuseaction #fb_.verbInfo.circuit#.#fb_.verbInfo.fuseaction#.");
        }

        // this is where the child <bean> verbs will store their data:
        fb_.verbInfo.beans = arrayNew(1);

	} else {
		// check to see if the user has requested that we re-use an existing copy of the bean factory in a persistent scope
		if (fb_.useexisting) {
			fb_.arPersistentScopes = arrayNew(1);
			// We'll go in order of narrowest to greatest scope
			arrayAppend(fb_.arPersistentScopes, "session");
			arrayAppend(fb_.arPersistentScopes, "application");
			arrayAppend(fb_.arPersistentScopes, "server");
			fb_.blnFoundBeanFactory = false;


			for (i = 1; i lt arrayLen(fb_.arPersistentScopes); i++) {


				if (structKeyExists(evaluate(fb_.arPersistentScopes[i]), fb_.coldspringfactory)) {
					// Now check its meta data to make sure this is really a Coldspring bean factory
					fb_.stMeta = getMetaData(evaluate("#fb_.arPersistentScopes[i]#.#fb_.coldspringfactory#"));
					if (fb_.stMeta.name eq "coldspring.beans.DefaultXmlBeanFactory") {
						fb_.blnFoundBeanFactory = true;
						fb_.sServiceFactoryInit = "#fb_.arPersistentScopes[i]#.#fb_.coldspringfactory#";
						break;
					}
				}
			}
			if (not fb_.blnFoundBeanFactory) {
				// User wanted to re-use something, but we couldn't find a valid object
				// Standard bean factory creation, like it always was
				fb_.sServiceFactoryInit = 'createObject("component", "coldspring.beans.DefaultXmlBeanFactory").init(defaultProperties="#fb_.defaultproperties#" )';
			}
		}
		else {
			// The user does not wish to re-use a Coldspring bean factory
			// Standard bean factory creation, like it always was
			fb_.sServiceFactoryInit = 'createObject("component", "coldspring.beans.DefaultXmlBeanFactory").init(defaultProperties="#fb_.defaultproperties#" )';
		}
		// set ColdSpring in this fusebox instance's application space
		fb_appendLine('<cfset myFusebox.getApplication().getApplicationData().#fb_.coldspringfactory# = #fb_.sServiceFactoryInit# />');
		fb_.i = 1;
		// load all bean definitions
		for ( fb_.i = 1; fb_.i lte arraylen( fb_.verbInfo.beans ); fb_.i = fb_.i + 1){
			fb_appendLine('<cfset myFusebox.getApplication().getApplicationData().#fb_.coldspringfactory#.loadBeansFromXmlFile( beanDefinitionFile="#fb_.verbInfo.beans[fb_.i]#" ) />');
		}
	}
</cfscript>